package com.example.lemoncommon.handler;


import com.example.lemoncommon.exception.ServiceException;
import com.example.lemoncommon.entity.Result;
import lombok.extern.slf4j.Slf4j;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.http.converter.HttpMessageNotReadableException;
import org.springframework.validation.ObjectError;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.MissingServletRequestParameterException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;

import javax.servlet.http.HttpServletRequest;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.List;
import java.util.stream.Collectors;

@Slf4j
@ControllerAdvice
public class GlobalExceptionHandler {


    /**

     * @return org.springframework.http.ResponseEntity<java.lang.Object>
     * @throws
     * @description: 异常信息打印
     */
    @ExceptionHandler(Exception.class)
    @ResponseBody
    public ResponseEntity<Object> defaultExceptionHandler(HttpServletRequest req, Exception e) {
        log.info("Error found:{}{}", e.getMessage(), e);
        //封装返回值
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        return new ResponseEntity<>(Result.ERROR(e.getMessage()),headers, HttpStatus.OK);
    }

    /**
     * @return org.springframework.http.ResponseEntity<java.lang.Object>
     */
    @ExceptionHandler(HttpMessageNotReadableException.class)
    @ResponseBody
    public ResponseEntity<Object> nullPointerExceptionHandler(Exception e) {
        //封装返回值
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        String detailMsg = null;
        try {
            detailMsg = e.getMessage().split("at")[0];
        } catch (Exception e1) {
            //这里只是尝试拿出详细信息，如果出错不予处理
            log.info("error message:", e);
        }
        headers.setContentType(MediaType.APPLICATION_JSON);
        return new ResponseEntity<>(Result.ERROR("400",detailMsg),headers, HttpStatus.OK);
    }



    /**
     * @return org.springframework.http.ResponseEntity<java.lang.Object>
     * @description: 参数类型错错误
     */
    @ExceptionHandler(MethodArgumentNotValidException.class)
    @ResponseBody
    public ResponseEntity<Object> methodArgumentNotValidExceptionHandler(MethodArgumentNotValidException e, HttpServletRequest req) {
        Enumeration<?> headerNames = req.getHeaderNames();
        HashMap<String, Object> headersMap = new HashMap<>(16);
        while (headerNames.hasMoreElements()) {
            String key = (String) headerNames.nextElement();
            String val = req.getHeader(key);
            headersMap.put(key, val);
        }

        //封装返回值
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        List<ObjectError> allErrors = e.getBindingResult().getAllErrors();
        String detailMsg = allErrors.stream().map(ObjectError::getDefaultMessage).collect(Collectors.joining(","));
        return new ResponseEntity<>(Result.ERROR("400",detailMsg),headers, HttpStatus.OK);
    }


    /**
     * @return org.springframework.http.ResponseEntity<java.lang.Object>
     */
    @ExceptionHandler(ServiceException.class)
    @ResponseBody
    public ResponseEntity<Object> exceptionHandler(ServiceException ex, HttpServletRequest request) {
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        return new ResponseEntity<>(Result.ERROR(ex.getReturnErrCode(),ex.getReturnErrMsg()),headers, HttpStatus.OK);
    }


    /**
     * @return org.springframework.http.ResponseEntity<java.lang.Object>
     */
    @ExceptionHandler(MissingServletRequestParameterException.class)
    @ResponseBody
    public ResponseEntity<Object> MissingServletRequestParameterExceptionHandler(MissingServletRequestParameterException ex, HttpServletRequest request) {
        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_JSON);
        return new ResponseEntity<>(Result.ERROR("400",ex.getMessage()),headers, HttpStatus.OK);
    }

}
